More Linux scratching.
authorrobertl <robertl@f51c46e8-681c-474f-0cfe-069cfd0219fb>
Sun, 17 Oct 2004 03:27:47 +0000 (03:27 +0000)
committerrobertl <robertl@f51c46e8-681c-474f-0cfe-069cfd0219fb>
Sun, 17 Oct 2004 03:27:47 +0000 (03:27 +0000)
Very weird.  This code worked once (for extremely liberal definitions of
"worked") , but successive runs fail.

Sent: 12
00 00 00 00 05 00 00 00 00 00 00 00
............
RX [16]:00 00 00 00 06 00 00 00 04 00 00 00 35 1a ff b3 ............5...(ACK     )

Synced in 0
Sent: 12
14 00 00 00 fe 00 00 00 00 00 00 00
............
RX [147]:14 00 00 00 ff 00 00 00 87 00 00 00 23 01 5e 01 47 50 53 4d 61 70 36 30 43 53 20 53 6f 66 74 77 61 72 65 20 56 65 72 73 69 6f 6e 20 33 2e 35 30 00 56 45 52 42 4d 41 50 20 52 65 63 72 65 61 74 69 6f 6e 61 6c 20 52 6f 75 74 61 62 6c 65 20 48 69 67 68 77 61 79 20 42 61 73 65 6d 61 70 2c 20 41 6d 65 72 69 63 61 73 20 76 32 20 32 2e 30 30 00 56 45 52 53 4d 41 50 20 4d 69 64 20 54 4e 2c 20 53 54 4c 2c 20 4c 27 76 69 6c 6c 65 20 30 2e 30 30 00 ................GPSMap60CS.Software.Version.3.50.VERBMAP.Recreational.Routable.Highway.Basemap..Americas.v2.2.00.VERSMAP.Mid.TN..STL..L.ville.0.00.(PRDDAT  )

Rx Data:[147]14 00 00 00 ff 00 00 00 87 00 00 00 23 01 5e 01 47 50 53 4d 61 70 36 30 43 53 20 53 6f 66 74 77 61 72 65 20 56 65 72 73 69 6f 6e 20 33 2e 35 30 00 56 45 52 42 4d 41 50 20 52 65 63 72 65 61 74 69 6f 6e 61 6c 20 52 6f 75 74 61 62 6c 65 20 48 69 67 68 77 61 79 20 42 61 73 65 6d 61 70 2c 20 41 6d 65 72 69 63 61 73 20 76 32 20 32 2e 30 30 00 56 45 52 53 4d 41 50 20 4d 69 64 20 54 4e 2c 20 53 54 4c 2c 20 4c 27 76 69 6c 6c 65 20 30 2e 30 30 00 ................GPSMap60CS.Software.Version.3.50.VERBMAP.Recreational.Routable.Highway.Basemap..Americas.v2.2.00.VERSMAP.Mid.TN..STL..L.ville.0.00.(PRDDAT  )
GPSMap60CS Software Version 3.50
ID:             291

Version:        3.50

RX [114]:14 00 00 00 fd 00 00 00 66 00 00 00 50 00 00 4c 01 00 41 0a 00 54 01 00 41 64 00 44 6d 00 41 c9 00 44 ca 00 44 6d 00 44 d2 00 41 2d 01 44 36 01 44 2d 01 41 90 01 44 6d 00 41 f4 01 44 f5 01 41 58 02 44 58 02 41 59 02 44 59 02 41 bc 02 44 bc 02 41 20 03 44 20 03 41 84 03 41 86 03 41 87 03 41 88 03 41 8b 03 44 8b 03 44 8c 03 44 8d 03 44 8e 03 ........f...P..L..A..T..Ad.Dm.A..D..Dm.D..A..D6.D..A..Dm.A..D..AX.DX.AY.DY.A..D..A..D..A..A..A..A..A..D..D..D..D..(PRTARR  )

Rx Data:[114]14 00 00 00 fd 00 00 00 66 00 00 00 50 00 00 4c 01 00 41 0a 00 54 01 00 41 64 00 44 6d 00 41 c9 00 44 ca 00 44 6d 00 44 d2 00 41 2d 01 44 36 01 44 2d 01 41 90 01 44 6d 00 41 f4 01 44 f5 01 41 58 02 44 58 02 41 59 02 44 59 02 41 bc 02 44 bc 02 41 20 03 44 20 03 41 84 03 41 86 03 41 87 03 41 88 03 41 8b 03 44 8b 03 44 8c 03 44 8d 03 44 8e 03 ........f...P..L..A..T..Ad.Dm.A..D..Dm.D..A..D6.D..A..Dm.A..D..AX.DX.AY.DY.A..D..A..D..A..A..A..A..A..D..D..D..D..(PRTARR  )
Capability 'P'.  Type 0
Capability 'L'.  Type 1
Capability 'A'.  Type 10
Capability 'T'.  Type 1
Capability 'A'.  Type 100
Capability 'D'.  Type 109
Capability 'A'.  Type 201
Capability 'D'.  Type 202
Capability 'D'.  Type 109
Capability 'D'.  Type 210
Capability 'A'.  Type 301
Capability 'D'.  Type 310
Capability 'D'.  Type 301
Capability 'A'.  Type 400
Capability 'D'.  Type 109
Capability 'A'.  Type 500
Capability 'D'.  Type 501
Capability 'A'.  Type 600
Capability 'D'.  Type 600
Capability 'A'.  Type 601
Capability 'D'.  Type 601
Capability 'A'.  Type 700
Capability 'D'.  Type 700
Capability 'A'.  Type 800
Capability 'D'.  Type 800
Capability 'A'.  Type 900
Capability 'A'.  Type 902
Capability 'A'.  Type 903
Capability 'A'.  Type 904
Capability 'A'.  Type 907
Capability 'D'.  Type 907
Capability 'D'.  Type 908
Capability 'D'.  Type 909
Capability 'D'.  Type 910
Sent: 14
14 00 00 00 0a 00 00 00 02 00 00 00 32 00
............2.
open: No such file or directory

gpsbabel/jeeps/gpslibusb.c

index d504384151cb48f3fbce070bd25b35c1593bb29e..b8c5868b4270b62b594609245ea1c611e1f5d5d2 100644 (file)
 
 #include <stdio.h>
 #include <usb.h>
+#include "gps.h"
 #include "garminusb.h"
 
 #define GARMIN_VID 0x91e
-#define TMOUT_W 1000 /*  Milliseconds to timeout device access. */
-#define TMOUT_R 0000 /*  Milliseconds to timeout device access. */
-#define TMOUT_I 0001 /*  Milliseconds to timeout device access. */
+
+/* This is very sensitive to timing; libusb and/or the unit is kind of
+ * sloppy about not obeying packet boundries.  If this is too high, the
+ * multiple packets responding to the device inquriy will be glommed into
+ * one packet and we'll misparse them.  If it's too low, we'll get partially
+ * satisfied reads.
+ */
+#define TMOUT_I 0015 /*  Milliseconds to timeout intr pipe access. */
 
 int gusb_intr_in_ep;
 int gusb_bulk_out_ep;
 int gusb_bulk_in_ep;
 
 static const char  oinit[12] = {0, 0, 0, 0, 0x05, 0, 0, 0, 0, 0, 0, 0};
-static const char oinit2[12] = {0, 0, 0, 0, 0x10, 0, 0, 0, 0, 0, 0, 0};
-static const char RQST[12] = {0x14, 0, 0, 0, 0xfe, 0, 0, 0, 0, 0, 0, 0};
-static char iresp[16];
-static char iresp2[16];
+garmin_usb_packet iresp;
 
 static struct usb_bus *busses;
 static usb_dev_handle *udev;
+static void garmin_usb_scan(void);
+static void garmin_usb_syncup(void);
 
 gusb_init(void)
 {
@@ -55,7 +60,7 @@ gusb_init(void)
        return 1;
 }
 
-dump(char *msg, unsigned char *in, int r)
+dump(char *msg, const unsigned char *in, int r)
 {
        int i;
        printf("%s: %d\n", msg, r);
@@ -73,18 +78,19 @@ int
 gusb_cmd_send(const garmin_usb_packet *opkt, size_t sz)
 {
        int r;
-        r = usb_bulk_write(udev, gusb_bulk_out_ep, &opkt->dbuf, sz, TMOUT_W);
-       dump ("Sent", &opkt->dbuf, r);
+
+        r = usb_bulk_write(udev, gusb_bulk_out_ep, &opkt->dbuf, sz, TMOUT_I);
+       dump ("Sent", &opkt->dbuf[0], r);
        if (r != sz) {
                fprintf(stderr, "Bad cmdsend\n");
        }
 }
-
+#if 0
 int
 gusb_cmd_get(garmin_usb_packet *ibuf, size_t sz)
 {
        int rv = 0;
-       unsigned char *obuf = ibuf->dbuf;
+       unsigned char *obuf = &ibuf->dbuf;
        unsigned char *buf = obuf;
 
        while (sz) {
@@ -115,6 +121,49 @@ gusb_cmd_get(garmin_usb_packet *ibuf, size_t sz)
        dump("completed intr Got", obuf, rv);
        return rv;
 }
+#else
+
+int
+gusb_cmd_get(garmin_usb_packet *ibuf, size_t sz)
+{
+       unsigned char *buf = &ibuf->dbuf[0];
+       unsigned char *obuf = buf;
+       int r = -1, tsz = 0;
+ while (r <= 0)
+       r = usb_interrupt_read(udev, gusb_intr_in_ep, buf, sz, TMOUT_I);
+
+       tsz = r;
+
+        if (gps_show_bytes) {
+               int i;
+                const char *m1, *m2;
+                printf("RX [%d]:", tsz);
+                for(i=0;i<tsz;i++)
+                        GPS_Diag("%02x ", obuf[i]);
+                for(i=0;i<tsz;i++)
+                        GPS_Diag("%c", isalnum(obuf[i])? obuf[i] : '.');
+
+                m1 = Get_Pkt_Type(ibuf->gusb_pkt.pkt_id[0], ibuf->gusb_pkt.databuf[0], &m2);
+                GPS_Diag("(%-8s%s)\n", m1, m2 ? m2 : "");
+                printf("\n");
+        }
+
+       return (r);
+
+
+}
+#endif
+
+void
+garmin_usb_teardown(void)
+{
+       if (udev) {
+               fprintf(stderr, "Tearing down\n");
+               usb_release_interface(udev, 0);
+               usb_close(udev);
+               udev = NULL;
+       }
+}
 
 garmin_usb_start(struct usb_device *dev)
 {
@@ -123,6 +172,7 @@ garmin_usb_start(struct usb_device *dev)
        char ibuf[4096];
 
        udev = usb_open(dev);
+       atexit(garmin_usb_teardown);
        if (!udev) { fatal("usb_open failed"); }
        /*
         * Hrmph.  No iManufacturer or iProduct headers....
@@ -158,11 +208,6 @@ garmin_usb_start(struct usb_device *dev)
 //printf("intr in: %d\n", gusb_intr_in_ep);
 
        garmin_usb_syncup();
-#if 0
-       cmd_send(RQST, sizeof(RQST));
-       cmd_get(ibuf, sizeof(ibuf));
-exit(0);
-#endif
 
 // fprintf(stdout, "====================================================\n");
 
@@ -172,10 +217,11 @@ exit(0);
        usb_close(udev);
 exit(1);
 }
-#if 1
+
+void
 garmin_usb_syncup(void)
 {
-       int maxct = 200;
+       int maxct = 5;
        int maxtries;
        char ibuf[4096];
 #if 0
@@ -185,27 +231,24 @@ garmin_usb_syncup(void)
 #endif
 
        for (maxtries = maxct; maxtries; maxtries--) {
-               gusb_cmd_send(oinit, sizeof(oinit));
-               gusb_cmd_get(iresp, sizeof(iresp));
-               if (iresp[4] == 6 && iresp[8] == 4) {
+
+                le_write16(&iresp.gusb_pkt.pkt_id, 0);
+                le_write32(&iresp.gusb_pkt.datasz, 0);
+                le_write32(&iresp.gusb_pkt.databuf, 0);
+
+               gusb_cmd_send((const garmin_usb_packet *) oinit, sizeof(oinit));
+               gusb_cmd_get(&iresp, sizeof(iresp));
+
+                if ((le_read16(iresp.gusb_pkt.pkt_id) == 6) &&
+                        (le_read32(iresp.gusb_pkt.datasz) == 4)) {
                        fprintf(stderr, "Synced in %d\n", maxct - maxtries);
 //                     fprintf(stderr, "Unit number %u\n", iresp[15] << 24 | iresp[14] << 16 | iresp[13] << 8 | iresp[12]);
                        return;
                }
        }
-#if 0
-       for (maxtries = maxct; maxtries; maxtries--) {
-               gusb_cmd_send(oinit2, sizeof(oinit2));
-               gusb_cmd_get(iresp2, sizeof(iresp2));
-               if (iresp2[4] == 0x11 && iresp2[8] == 4) {
-                       return;
-               }
-       }
-#endif
-fprintf(stderr, "Cannot sync up with receiver\n");
-exit(1);
+return;
+       fatal("Cannot sync up with receiver\n");
 }
-#endif
 
 static
 void garmin_usb_scan(void)
@@ -228,11 +271,4 @@ void garmin_usb_scan(void)
        }
 }
 
-#if 0
-Xmain()
-{
-               garmin_usb_init();
-               garmin_usb_scan();
-}
-#endif
 #endif /* !defined(NO_USB) */